package com.example.linktestapplication.ui;

import android.content.Context;
import android.graphics.Canvas;
import android.graphics.Color;
import android.graphics.Paint;
import android.graphics.drawable.Drawable;
import android.util.AttributeSet;
import android.util.Log;
import android.view.GestureDetector;
import android.view.MotionEvent;
import android.view.View;

import androidx.annotation.NonNull;
import androidx.annotation.Nullable;

import com.example.linktestapplication.R;

public class TouchSensing extends View {
    private Paint backgroundPaint;
    private Paint innerCyclePaint;
    private Paint outerCyclePaint;

    private Drawable leftDrawable;
    private Drawable topDrawable;
    private Drawable rightDrawable;
    private Drawable bottomDrawable;

    private TouchCallback touchCallback;

    public TouchSensing(Context context) {
        this(context, null);
    }

    public TouchSensing(Context context, @Nullable AttributeSet attrs) {
        this(context, attrs, 0);
    }

    public TouchSensing(Context context, @Nullable AttributeSet attrs, int defStyleAttr) {
        this(context, attrs, defStyleAttr, 0);
    }

    public TouchSensing(Context context, @Nullable AttributeSet attrs, int defStyleAttr, int defStyleRes) {
        super(context, attrs, defStyleAttr, defStyleRes);
        init();
    }


    private void init() {

        backgroundPaint = new Paint();
        backgroundPaint.setStrokeWidth(dp2px(1f));
        backgroundPaint.setStyle(Paint.Style.FILL);
        backgroundPaint.setColor(Color.GRAY);
        backgroundPaint.setAntiAlias(true);


        leftDrawable = getResources().getDrawable(R.mipmap.arrows_left);
        rightDrawable = getResources().getDrawable(R.mipmap.arrows_right);
        topDrawable = getResources().getDrawable(R.mipmap.arrows_up);
        bottomDrawable = getResources().getDrawable(R.mipmap.arrows_down);


    }

    /**
     * sp值转换为px值
     */
    public float sp2px(float spValue) {
        final float fontScale = getContext().getResources().getDisplayMetrics().scaledDensity;
        return spValue * fontScale + 0.5f;
    }

    /**
     * change dp to px
     *
     * @param dpValue
     * @return
     */
    public int dp2px(float dpValue) {
        float scale = getContext().getResources().getDisplayMetrics().density;
        return (int) (dpValue * scale + 0.5f);
    }


    public void setTouchCallback(TouchCallback touchCallback) {
        this.touchCallback = touchCallback;
    }

    private float downX, downY;

    private float centerX, centerY;

    private long oldTime;
    private long currentTime;
    private GestureDetector gestureDetector;

    @Override
    protected void onLayout(boolean changed, int left, int top, int right, int bottom) {
        super.onLayout(changed, left, top, right, bottom);
        centerX = (float) (right - left) / 2;
        centerY = (float) (bottom - top) / 2;

        cycleRadius = (float) getWidth() / 2 - dp2px(8f);
        cycleTop = top + dp2px(8f);
        cycleBottom = bottom - dp2px(8f);
        cycleLeft = dp2px(8f);
        cycleRight = right - dp2px(8f);
        Log.i("TAG", "onLayout: left = " + left + ",right = " + right + ",top = " + top + ",bottom = " + bottom);
    }

    @Override
    public boolean onTouchEvent(MotionEvent event) {
        getParent().requestDisallowInterceptTouchEvent(true);//解决滑动冲突

        switch (event.getAction()) {
            case MotionEvent.ACTION_DOWN:
                downX = event.getX();
                downY = event.getY();

                break;
            case MotionEvent.ACTION_MOVE:
                currentTime = System.currentTimeMillis();
                if (currentTime - oldTime > 50) {
                    downX = event.getX();
                    downY = event.getY();

                    if (touchCallback != null && touchInCycle(downX, downY)) {

                        Log.i("TAG", "onTouchEvent: send");
                        touchCallback.startMove((downX - centerX) / ((float) getWidth() / 2), (centerY - downY) / ((float) getHeight() / 2));
                    }

                    oldTime = currentTime;

                }


                break;
            case MotionEvent.ACTION_UP:

                if (touchCallback != null) {
                    touchCallback.endMove();
                }

                break;

        }
        return true;
    }

    private boolean touchInCycle(float x, float y) {
        float dx = Math.abs(x - centerX);
        float dy = Math.abs(y - centerY);

        return (dx * dx + dy * dy) <= (cycleRadius * cycleRadius);
    }

    private float cycleTop;
    private float cycleBottom;
    private float cycleRight;
    private float cycleLeft;
    private float cycleRadius;


    @Override
    protected void onDraw(@NonNull Canvas canvas) {
        super.onDraw(canvas);

        canvas.drawCircle((float) getWidth() / 2, (float) getHeight() / 2, cycleRadius, backgroundPaint);

        topDrawable.setBounds((int) (centerX - (float) topDrawable.getMinimumWidth() / 2),
                dp2px(8) * 2,
                (int) (centerX + (float) topDrawable.getMinimumWidth() / 2),
                topDrawable.getMinimumHeight() + dp2px(8));
        topDrawable.draw(canvas);

        rightDrawable.setBounds((int) (getWidth() - (float) rightDrawable.getMinimumWidth() - dp2px(8f) * 2),
                (int) ((float) getHeight() / 2 - (float) rightDrawable.getMinimumHeight() / 2),
                (getWidth() - dp2px(8f) * 2),
                (int) ((float) getHeight() / 2 + (float) rightDrawable.getMinimumHeight() / 2));
        rightDrawable.draw(canvas);
        Log.i("TAG", "onDraw: right rect = " + rightDrawable.getBounds());

        bottomDrawable.setBounds((int) (centerX - (float) bottomDrawable.getMinimumWidth() / 2),
                getHeight() - dp2px(8) * 2 - bottomDrawable.getMinimumHeight(),
                (int) (centerX + (float) bottomDrawable.getMinimumWidth() / 2),
                getHeight() - dp2px(8) * 2);
        bottomDrawable.draw(canvas);

        leftDrawable.setBounds(dp2px(8f) * 2,
                (int) ((float) getHeight() / 2 - (float) leftDrawable.getMinimumHeight() / 2),
                dp2px(8f) * 2 + leftDrawable.getMinimumWidth(),
                (int) ((float) getHeight() / 2 + (float) leftDrawable.getMinimumHeight() / 2));
        leftDrawable.draw(canvas);
        Log.i("TAG", "onDraw: left rect = " + leftDrawable.getBounds());

    }

    public interface TouchCallback {
        void startMove(float xAspect, float yAspect);

        void endMove();
    }
}
